package com.cangshi.controller;

import com.alibaba.fastjson.JSON;
import com.cangshi.entity.CorrectJSONObject;
import com.cangshi.entity.JSONException;
import com.cangshi.entity.User;
import com.cangshi.entity.UserEntity;
import com.cangshi.mail.MailManage;
import com.cangshi.permission.entity.Token;
import com.cangshi.permission.entity.UserSubject;
import com.cangshi.permission.exception.LoginFailedException;
import com.cangshi.permission.saver.SubjectHolder;
import com.cangshi.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;
import sun.misc.BASE64Decoder;

import javax.servlet.http.HttpServletRequest;
import java.io.FileOutputStream;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Random;

/**
 * Created by 15c on 2017/4/3.
 */
@Controller
@RequestMapping("/users")
public class UserController {
    @Autowired
    UserService userService;

    /**
     * 用户通过手机号注册
     *
     * @param telnumber        电话号码
     * @param password         密码
     * @param verificationCode 验证码
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/register/tel", method = RequestMethod.POST, produces = "text/html;charset=UTF-8")
    String registerByTelPhone(@RequestParam(required = false) String telnumber,
                              @RequestParam(required = false) String password,
                              @RequestParam(required = false) String verificationCode) {
        // 判断参数是否完整。
        if (telnumber == null || password == null) {
            throw new JSONException(100, "用户名或密码参数不完整");
        }
        // 判断参事值是否为空。
        if (telnumber.equals("") || password.equals("")) {
            throw new JSONException(101, "用户名或密码为空");
        }
        User telUser = new User();
        telUser.setUserTelphone(telnumber);
        User user = userService.selectUserIdByTelphone(telUser);
        // 判断telPhone是否已经注册(通过查询TelPhone，看是否存在)
        if (user != null) {
            throw new JSONException(102, "电话号码已被注册");
        }
        telUser.setUserPassword(password);
        int result = userService.addUserByTelphone(telUser);
        //数据库插入成功返回1
        if (result != 1) {
            throw new JSONException(200, "注册失败");
        }

        return new CorrectJSONObject("用户注册成功").toString();
    }

    /**
     * 获取验证码
     *
     * @param email 邮箱
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/getVerificationCode", method = RequestMethod.GET, produces = "text/html;charset=UTF-8")
    String getVerificationCode(@RequestParam(required = false) String email) {
        if (null == email) {
            throw new JSONException(101, "email参数为空");
        }
        if ("".equals(email)) {
            throw new JSONException(102, "email账号值为空");
        }
        //发送验证码到邮箱
        MailManage.addMail(email).newThreadToSentEmailForCheck();
        CorrectJSONObject correctJSONObject = new CorrectJSONObject("生成发送验证码成功");
        correctJSONObject.setData(0);
        return correctJSONObject.toString();
    }


    /**
     * 用户通过邮箱注册
     *
     * @param email            邮箱
     * @param password         密码
     * @param verificationCode 验证码
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/register/email", method = RequestMethod.POST, produces = "text/html;charset=UTF-8")
    String registerByEmail(@RequestParam(required = false) String email,
                           @RequestParam(required = false) String password,
                           @RequestParam(required = false) String verificationCode) {

        // 判断参数是否完整。
        if (null == email || null == password || null == verificationCode) {
            throw new JSONException(100, "用户名或密码或验证码参数不完整");
        }
        // 判断参事值是否为空。
        if (email.equals("") || password.equals("") || verificationCode.equals("")) {
            throw new JSONException(101, "用户名或密码验证码为空");
        }

        //获得当前邮箱信息
        MailManage.MailEntity mailEntity = MailManage.getMail(email);
        // 若已发出验证码，则不会空，否则反之
        if (mailEntity == null) {
            throw new JSONException(108, "用户尚未获取验证码");
        }
        //获取生成的验证码
        String checkNum = mailEntity.getMailCheckString();

        if (!checkNum.equals(verificationCode)) {
            throw new JSONException(109, "验证码输入错误");
        }
        User emailUser = new User();
        emailUser.setUserEmail(email);
        User user = userService.selectUserIdByuserEmail(emailUser);
        // 判断email是否已经注册(通过查询email，看是否存在)
        if (user != null) {
            throw new JSONException(102, "邮箱号已被注册");
        }
        emailUser.setUserPassword(password);
        int result = userService.addUserByEmail(emailUser);
        //数据库插入成功返回1
        if (result != 1) {
            throw new JSONException(200, "注册失败");
        }
        return new CorrectJSONObject("用户注册成功").toString();
    }

    /**
     * 用户登录
     *
     * @param username （可代表telPhone或者email，在后面UserSubject类中的login方法中调用checkWithToken方法进行判断）
     * @param password 密码
     * @return
     */

    @ResponseBody
    @RequestMapping(value = "/login", method = RequestMethod.POST, produces = "text/html;charset=UTF-8")
    String login(@RequestParam(required = false) String username,
                 @RequestParam(required = false) String password) {
        // 判断参数是否完整。
        if (username == null || password == null) {
            throw new JSONException(100, "用户名或密码参数不完整");
        }
        if ("".equals(username) || "".equals(password)) {
            throw new JSONException(102, "用户名或密码为空");
        }
        // 获取当前访问对象
        UserSubject subject = (UserSubject) SubjectHolder.getSubject();

        String authorization = null;
        try {
            // 登录，并获取证书
            authorization = subject.login(new Token(username, password));
            CorrectJSONObject correctJSONObject = new CorrectJSONObject("登录成功");

            // 设置返回json
            correctJSONObject.setData(authorization);
            return correctJSONObject.toString();

        } catch (LoginFailedException e) {
            throw new JSONException(103, e.getMessage());
        }

    }

    /**修改功能
     * 用于用户通过忘记密码时的重置密码（手机号）
     *
     * @param telPhone 用户名
     * @param newpassword      新密码
     * @param verificationCode 验证码
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/resetPasswordByTelPhone", method = RequestMethod.POST, produces = "text/html;charset=UTF-8")
    String userResetPasswordByTelPhone(@RequestParam(required = false) String telPhone,
                             @RequestParam(required = false) String newpassword,
                             @RequestParam(required = false) String verificationCode) {
        // 判断参数是否完整。
        if (null == telPhone || null == newpassword) {
            throw new JSONException(100, "用户名或新密码或验证码参数不完整");
        }
        // 判断参事值是否为空。
        if ("".equals(telPhone) || "".equals(newpassword)) {
            throw new JSONException(101, "用户名或密码或验证码为空");
        }
        //new 一个resetUser对象来查询用户对应id
        User resetUser = new User();
        resetUser.setUserTelphone(telPhone);
        //通过Telphone或者userEmail查询用户对应id，如果没查到则表示该用户还没有注册。
        //通过new 一个resultUser来接收查询到的user对象，从而通过resultUser.getUserId()来获得用户对应id。
        User resultUser = userService.selectUserIdByTelphone(resetUser);
        if (resultUser == null) {
                throw new JSONException(201, "该用户还未注册");
        }
        //最后new一个finalUser对象来实现用户密码的修改。
        User finalUser = new User();
        finalUser.setUserId(resultUser.getUserId());
        finalUser.setUserPassword(newpassword);

        int i = userService.updatePasswordByUserId(finalUser);
        if (i != 1) {
            throw new JSONException(202, "修改密码失败");
        }
        return new CorrectJSONObject("用户修改密码成功").toString();
    }
    /**新功能
     * 用于用户通过忘记密码时的重置密码（邮箱号）
     *
     * @param email 用户名
     * @param newpassword      新密码
     * @param verificationCode 验证码
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/resetPasswordByEmail", method = RequestMethod.POST, produces = "text/html;charset=UTF-8")
    String userResetPasswordByEmail(@RequestParam(required = false) String email,
                             @RequestParam(required = false) String newpassword,
                             @RequestParam(required = false) String verificationCode) {
        // 判断参数是否完整。
        if (null == email || null == newpassword||null==verificationCode) {
            throw new JSONException(100, "用户名或新密码或验证码参数不完整");
        }
        // 判断参事值是否为空。
        if ("".equals(email) || "".equals(newpassword)||"".equals(verificationCode)) {
            throw new JSONException(101, "用户名或密码或验证码为空");
        }
        //new 一个resetUser对象来查询用户对应id
        User resetUser = new User();
        resetUser.setUserEmail(email);
        //通过userEmail查询用户对应id，如果没查到则表示该用户还没有注册。
        //通过new 一个resultUser来接收查询到的user对象，从而通过resultUser.getUserId()来获得用户对应id。
        User  resultUser = userService.selectUserIdByuserEmail(resetUser);
        if (resultUser == null) {
            throw new JSONException(201, "该用户还未注册");
        }
        //获得当前邮箱信息
        MailManage.MailEntity mailEntity = MailManage.getMail(email);
        // 若已发出验证码，则不会空，否则反之
        if (mailEntity == null) {
            throw new JSONException(108, "用户尚未获取验证码");
        }
        //获取生成的验证码
        String checkNum = mailEntity.getMailCheckString();

        if (!checkNum.equals(verificationCode)) {
            throw new JSONException(109, "验证码输入错误");
        }

        //最后new一个finalUser对象来实现用户密码的修改。
        User finalUser = new User();
        finalUser.setUserId(resultUser.getUserId());
        finalUser.setUserPassword(newpassword);

        int i = userService.updatePasswordByUserId(finalUser);
        if (i != 1) {
            throw new JSONException(202, "修改密码失败");
        }
        return new CorrectJSONObject("用户修改密码成功").toString();
    }



    /**
     * 用于用户修改自己的信息
     *
     * @param user user对象其中需要包含userId。
     * @return
     */
    @ResponseBody
    @RequestMapping(value = "/details/revise", method = RequestMethod.POST, produces = "text/html;charset=UTF-8")
    String userReviseInfo(@RequestBody(required = false) User user) {

        // 获取当前访问对象
        UserSubject subject = (UserSubject) SubjectHolder.getSubject();
        //获取当前的登录信息
        UserEntity userEntity = (UserEntity) subject.getAuthorizationEntity();
        //获取当前的用户登录id
        int userId = userEntity.getUserId();
        //判断user参数是否为空
        if (null == user) {
            throw new JSONException(104, "参数为空");
        }
        if (null == user.getUserId()) {
            throw new JSONException(107, "未指定欲修改用户Id");
        }
        if (userId != user.getUserId()) {
            throw new JSONException(106, "没有权限修改该用户信息");
        }

        int result = userService.updateUserPrivateInfoByUserId(user);
        if (1 != result) {
            throw new JSONException(205, "上传失败");
        }


        return new CorrectJSONObject("修改成功").toString();


    }


    /**
     * 用于展示用户的基本信息
     *
     * @return resultUser的json数据
     */
    @ResponseBody
    @RequestMapping(value = "/details/show", method = RequestMethod.GET, produces = "text/html;charset=UTF-8")
    String userShowInfo() {

        // 获取当前访问对象
        UserSubject subject = (UserSubject) SubjectHolder.getSubject();

        //获取当前的登录信息
        UserEntity userEntity = (UserEntity) subject.getAuthorizationEntity();
        //获取当前的用户登录id
        int userId = userEntity.getUserId();

        User resultUser = userService.selectUserPartInfoByUserId(userId);

        if (null == resultUser) {
            throw new JSONException(203, "查询信息失败");
        }
        CorrectJSONObject object = new CorrectJSONObject("获取用户信息成功");
        object.setData(resultUser);

        return object.toString();
    }

    /**
     * 用于一个用户查看另外一个用户的基本信息
     *
     * @param userId return resultUser的json数据
     */
    @ResponseBody
    @RequestMapping(value = "/showOther", method = RequestMethod.GET, produces = "text/html;charset=UTF-8")
    String userShowOtherInfo(@RequestParam(required = false) Integer userId) {
        if (null == userId) {
            throw new JSONException(101, "参数不存在");
        }
        User resultUser = userService.selectUserPartInfoByUserId(userId);
        if (null == resultUser) {
            throw new JSONException(110, "用户Id不存在");
        }
        CorrectJSONObject object = new CorrectJSONObject("获取用户信息成功");
        object.setData(resultUser);

        return object.toString();

    }

    //分页

    // 获取一共有好多条数据
    // 规定10条1页
    // 通过查询语句查询 order by task_time desc
    //                limit 0,10
    // service.selectList(userId,page)
    // 返回：list<task>,error,msg,allPage

//    CorrectJSONObject correctJSONObject = new CorrectJSONObject("获取成功");
//    correctJSONObject.setData(list);
//    correctJSONObject.put("allpage", 20);
//
//    correctJSONObject
//    return correctJSONObject.toString();

    /**
     * 用户图片上传入口
     *
     * @param request 用户请求
     * @param image   图片
     * @return 结果json
     */
    @ResponseBody
    @RequestMapping(value = "/details/image-upload", method = RequestMethod.POST, produces = "text/html;charset=UTF-8")
    public String imageUpload(HttpServletRequest request, @RequestBody String image) {

        //指定头类型
        String header = "data:image/png;base64,";


        //获取服务器的路径
        String realPath = request.getSession().getServletContext().getRealPath("/resources/img");

        //声明图片地址
        String imgAddress = null;

        //获取文件名
        //String originalFilename = image.getOriginalFilename();

        //获取扩展名
        String extensionName = ".png";
        System.out.println("--------------->" + extensionName);

        //判断文件格式是否正确
        if (image == null || image.indexOf(header) != 0) {

            //返回错误信息
            throw new JSONException(103, "文件不存在或格式不正确");

        } else {

            //去掉头部
            image = image.substring(header.length());

            BASE64Decoder decoder = new BASE64Decoder();

            try {
                if (!image.isEmpty()) {

                    //以当前时间加随机数命名上传文件
                    SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddhhmmssSSS");
                    String date = sdf.format(new java.util.Date());


                    //设置图片名为当前时间加随机数
                    imgAddress = date + new Random().nextInt() + extensionName;

                    //将文件上传到服务器
                    byte[] decodedBytes = decoder.decodeBuffer(image);

                    FileOutputStream out = new FileOutputStream(realPath + "/" + imgAddress);

                    out.write(decodedBytes);

                    out.close();

                    //设置返回结果
                    CorrectJSONObject correctJSONObject = new CorrectJSONObject("上传成功");
                    correctJSONObject.setData(imgAddress);
                    return JSON.toJSONString(correctJSONObject);

                } else {

                    throw new JSONException(105, "上传的文件不存在");

                }
            } catch (IOException e) {

                throw new JSONException(203, e.getMessage());

            }
        }

    }


}

